CFnと手動でCodeDeployをコンテンツ上書きオプションで実行する
おはようございます、もきゅりんです。
先日、今更ですが、CodeDeployでコンテンツ上書きオプションについて知る機会がありました。
Blue/Greenデプロイ他、コンテナでのデプロイ環境も整ってきているため、あまり利用機会もないようにも思えますが、まとめておきます。
自分はこれまで、既存ファイルがある場合、scripts/beforeInstall.bash
とかで全消ししてファイルを追加する、だったりBlue/Greenデプロイで対応していました。
この件、改めて調べてみると、結構長い間、appspec.yml
で対応してくれよ、ずっと待ってる...というやり取りがなされていたようです。
Add Support for "Overwrite" instruction in appspec.yml "Files" section #14
とりあえず、やってみて説明を挟んでいこうと思います。
なお、Bule / Greenデプロイに興味・関心ある際はこちらをご確認下さい。
目次
- 構成
- 前提
- やること
- 1. PackerでAMIを作成
- 2. CFnでCodePipelineを構築
- 3. CodeDeployを手動で再デプロイ
- 4. GitHub上のファイルを更新して確認
- 5. やっていることの説明
- 参考/紹介
構成
構成は以下となります。 複数インスタンスにする必然性はなかったのですが、折角LBも含めたし、ということで冗長化してみました。
前提
- Packerが使えること
-
AWS CLIが利用できること
-
GitHubリポジトリが利用できてPersonal access tokensを取得していること
-
上記GitHubのaccess tokensをSecrets Managerに格納していること
不足していた場合、これらについては下記記事を参考にしてみて下さい。
[小ネタ] SecretsManagerを使ってCFnのGitHubTokenをシークレットにする
やること
- PackerでAMIを作成
- CFnでCodePipelineを構築
- CodeDeployを手動で再デプロイ
- GitHub上のファイルを何か更新して確認
- やっていることの説明
起動するインスタンスのAMIはPackerで作成して、AWSの構成はCFnで作成します。
利用するファイルは下記GitHubに格納されています。
上記を任意のディレクトリに保存します。テンプレート等を格納したファイルは以下の構成です。
$ tree . ├── CFnTemplate │ ├── demo.template.yml │ ├── deploy.sh │ └── envfile ├── Packer │ └── packer-nginx.json ├── appspec.yml └── index.html
こちらをご自身のGitHubリポジトリにForkするとか別途Pushするなどして下さい。
1. PackerでAMIを作成
19行目の YOUR_PROFILE
は自身の ~/.aws/config
のprofileをご確認下さい。
MFA入力が必要だとして、以下コマンドで作成します。
123456は実際のtokenを入力して下さい。
packer build -var "mfa_code=123456" Packer/packer-nginx.json
作成されたら、IDを取得して控えます。
aws ec2 describe-images --filters "Name=name,Values=demo-nginx-ami" --query 'Images[*].{ID:ImageId}'
参考:
2. CFnでCodePipelineを構築
CFnTEmplate/envfile
を更新していきます。
AMIIDに先ほど控えたAMIIDを記入します。
EC2のキーペア名を記入します。
CodePipelineでデプロイするための情報を記入します。
(GitHubSecretは何でも良いです。)
# e.g. export GitHubRepositoryName=codedeploy-overwrite export GitHubAccountName=cmoqrin export GitHubSecret=secret export Branch=master export ApplicationName=Application export DeploymentGroupName=DeploymentGroup export PipelineName=CodePipeline
テンプレート内の OAuthToken
をSecrets Managerで設定したものに更新します。
参考:
[小ネタ] SecretsManagerを使ってCFnのGitHubTokenをシークレットにする
そしたらスタックを作成します。
cd CFnTemplate ./deploy.sh
5分くらいで完了するはずです。
CodePipelineを見にいきます。
ここでも5分くらい待ちます。。
失敗しました。
詳細リンクから確認しにいきましょう。
3. CodeDeployを手動で再デプロイ
既にファイルがあるよって叱られていますね。
では、そのデプロイIDを元に手動で再デプロイしにいきましょう。
デプロイグループのオーバーライドからコンテンツの上書きを選んでデプロイします。
ここからまた10分ほど待ちます。。(1台4,5分です。。)
成功です。
では、ALBのDNS名からブラウザで確認してみましょう。
確認できましたー
4. GitHub上のファイルを更新して確認
index.html
を編集してGitにPushしてみましょう。
また、10分くらい。。
確認できました2ー
5. やっていることの説明
何度読んでもいまいち理解しにくかったので、整理しておきます。
要点は下記2点です。
- CodeDeployでロールバックが出来ること
- 既存のコンテンツのロールバック動作を手動で設定できること
まず、1点目ですが、CodeDeployのロールバックは自動ロールバックおよび手動ロールバックが可能です。
手動ロールバックは一旦今回は関係ないので置いておきます。
自動ロールバックについては、以下のいずれかまたは両方を選択してロールバックを実行できます。
- デプロイが失敗したときにロールバックする
- アラームのしきい値が一致したときにロールバック
2点目、既存のコンテンツのロールバック動作です。
CodeDeploy を使用した再デプロイおよびデプロイのロールバックには、このように記載されています。
CodeDeploy エージェントは、前回のデプロイでインストールされたすべてのファイルを各インスタンスから削除します。
前回のデプロイに含まれていないファイルがデプロイ先に表示された場合は、次回のデプロイ時にこれらのファイルを
CodeDeployで処理する方法を選択できます。
下記の中から既存のコンテンツのロールバック動作を選択できます。
- Fail the deployment(失敗)
- コンテンツの上書き
- コンテンツの保持
さて、デプロイが失敗したときにロールバックする、を設定してデプロイを実行しました。
既存にファイルが含まれると失敗します。
該当のデプロイに対して、次回デプロイ時の既存コンテンツのロールバック動作を「コンテンツの上書き」に設定して手動で再度デプロイし直します。
初回のデプロイのため、どのファイルもデプロイリストには含まれていません。もちろん、既存のファイルもデプロイリストには含まれていません。
ということで、2点目で説明した既存コンテンツのロールバック設定から、既存のコンテンツを上書きします。
次回からは、上書きされたファイルはデプロイリストに含まれるため、ファイルは正常にデプロイされます。
自分はなかなか理解しにくくかったので、まとめてみました。
今回は待ちが長くてしんどかったですね。。
(コンテナのデプロイの速さに慣れていたため逆にビックリしました。。)
以上です、どなたかのお役に立てば幸いです。